package guava;

import com.google.common.base.Ticker;
import com.google.common.cache.*;
import com.google.common.collect.MapMaker;
import com.google.common.util.concurrent.Callables;
import org.junit.Test;
import org.xukai.common.ComparableStudent;

import java.util.concurrent.ConcurrentMap;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;

/**
 * @author xukai
 * @desc
 * @date 2016-12-03-下午 2:33
 */
public class CacheUtil {

    /**
     * MapMaker
     */
    @Test
    public void MapMakerTest(){
        ConcurrentMap<String,ComparableStudent> books = new MapMaker().concurrencyLevel(2) //并发级别,即允许最多2个线程并发更新, 默认值为4
                .weakKeys() //使用SoftReference引用对象包装value
                .makeMap(); //构建Map对象
    }

    /**
     * Cache
     */
    @Test
    public void CacheTest() throws Exception {
        Cache<Object, Object> cache = Cache2.callableCached();
        cache.get("2", Callables.returning("")); //同步方式获取不存在的key缓存
        cache.getIfPresent("2");
    }

    /**
     * CacheBuild
     */
    @Test
    public void CacheBuildTest(){
        LoadingCache<String,ComparableStudent> tradeAccountCache =
                CacheBuilder.newBuilder()
                        .concurrencyLevel(10)
                        .expireAfterWrite(5L, TimeUnit.MINUTES)
                        .maximumSize(5000L).softValues()//使用SoftReference对象封装value, 使得内存不足时，自动回收
                        .ticker(Ticker.systemTicker())//定义缓存对象失效的时间精度为纳秒级
                        .build(new CacheLoader<String, ComparableStudent>() {
                            @Override
                            public ComparableStudent load(String key) throws  Exception {
                                return null;
                            }
                        });
        String spec = "concurrencyLevel=10,expireAfterAccess=5m,softValues";
        CacheBuilderSpec cacheBuilderSpec =
                CacheBuilderSpec.parse(spec);
        CacheBuilder cacheBuilder =
                CacheBuilder.from(cacheBuilderSpec);
        cacheBuilder.ticker(Ticker.systemTicker())
                .build(new CacheLoader<String, ComparableStudent>() {
                    @Override
                    public ComparableStudent load(String key) throws
                            Exception {
                        return null;
                    }
                });
    }

    /**
     * CacheLoader
     */
    @Test
    public void CacheLoaderTest(){
//        CacheLoader<Key,value> cacheLoader =CacheLoader.from(Function<Key,Value> func);
//        CacheLoader<Object,Value> cacheLoader = CacheLoader.from(Supplier<Value> supplier);
    }

    /**
     * RemovalListeners
     * This step should occur before we register our  RemovalListener object with the CacheBuilder instance
     */
    @Test
    public void  RemoveListenerTest(){
        RemovalListener<String,ComparableStudent> myRemovalListener = new RemovalListener<String, ComparableStudent>() {
                    @Override
                    public void onRemoval(RemovalNotification<String,ComparableStudent> notification) {
                        //Do something here
                    }
                };
        RemovalListener<String,ComparableStudent> removalListener =
                RemovalListeners.asynchronous(myRemovalListener, Executors.newFixedThreadPool(4));
    }
}
